package cn.vehicle.biz.core.support.impl;

import cn.vehicle.biz.core.support.abs.AbstractSupport;
import cn.vehicle.domains.ctx.PlateDetectContext;
import cn.vehicle.domains.entity.CommonVehicleEntity;
import cn.vehicle.domains.entity.TransportVehicleEntity;
import cn.vehicle.domains.entity.VehicleCommonLedgerEntity;
import cn.vehicle.domains.entity.VehicleTransportLedgerEntity;
import cn.vehicle.enums.EmissionStandardEnum;
import cn.vehicle.enums.GovUploadStatus;
import cn.vehicle.enums.VehicleTypeEnum;
import cn.vehicle.exception.VehicleAccessException;
import cn.vehicle.service.TransportVehicleService;
import cn.vehicle.service.VehicleCommonLedgerService;
import cn.vehicle.service.VehicleTransportLedgerService;
import cn.vehicle.service.config.SystemConfig;
import cn.vehicle.service.config.SystemConfigService;
import jakarta.annotation.Resource;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;


/**
 * 运输车辆识别业务支持类
 * <p>
 * 继承自 {@link AbstractSupport}，用于处理运输车辆的进出场识别与台账记录逻辑。
 * 提供排放标准校验、进场权限判断、出场记录维护等核心业务。
 * </p>
 *
 * <p>主要功能：</p>
 * <ul>
 *   <li>校验运输车辆信息合法性；</li>
 *   <li>判断排放标准与进场控制；</li>
 *   <li>记录运输车辆进出场台账；</li>
 *   <li>维护普通车辆与运输车辆的台账关联。</li>
 * </ul>
 */
@Service
@Slf4j
public class TransportSupport extends AbstractSupport {

    @Resource
    private TransportVehicleService transportVehicleService;

    @Resource
    private VehicleTransportLedgerService vehicleTransportLedgerService;

    @Resource
    private VehicleCommonLedgerService vehicleCommonLedgerService;

    @Resource
    private SystemConfigService systemConfigService;

    /**
     * 返回当前支持类的车辆类型标识
     *
     * @return 运输车辆类型名称（TRANSPORT）
     */
    @Override
    public String supportName() {
        return VehicleTypeEnum.TRANSPORT.name();
    }

    /**
     * 处理运输车辆进场逻辑
     * <p>
     * 校验车辆是否存在、排放标准是否达标，以及是否允许进场。
     * 若车辆不符合要求则抛出异常。
     * </p>
     *
     * @param plateDetectContext 车牌识别上下文对象，包含车辆与相机识别信息
     */
    @Override
    public void processIn(PlateDetectContext plateDetectContext) {
        super.processIn(plateDetectContext);

        // 从识别上下文中获取普通车辆信息（包含关联的运输车辆ID）
        CommonVehicleEntity commonVehicleEntity = plateDetectContext.getCommonVehicleEntity();

        // 查询关联的运输车辆信息，若不存在则抛出异常
        TransportVehicleEntity transportVehicleEntity = transportVehicleService.getTransportVehicleById(commonVehicleEntity.getAssociationId());
        if (transportVehicleEntity == null) {
            throw VehicleAccessException.DATE_NOT_EXIST.newInstance("车辆不存在");
        }
        plateDetectContext.setTransportVehicleEntity(transportVehicleEntity);

        //在不在黑名单车辆里面


        // 校验排放标准是否符合系统配置要求
        EmissionStandardEnum emissionStandardEnum = EmissionStandardEnum.valueOf(systemConfigService.get(SystemConfig.emissionStandard));
        if (emissionStandardEnum.getIndex() < EmissionStandardEnum.valueOf(transportVehicleEntity.getEmissionStandard()).getIndex()) {
            throw VehicleAccessException.SYSTEM_ERROR.newInstance("车辆排放标准不符合要求");
        }

        // 判断系统是否允许运输车辆进场（全局进场管控）
        if (!systemConfigService.get(SystemConfig.transportEntryControl)) {
            throw VehicleAccessException.SYSTEM_ERROR.newInstance("车辆不允许进入, 全部管控");
        }

        // 记录允许进场的日志
        log.info("运输车辆可以进入 vehicleNumber:{}", commonVehicleEntity.getVehicleNumber());

    }

    /**
     * 处理运输车辆出场逻辑
     * <p>
     * 校验车辆是否存在并绑定运输信息，防止无效出场。
     * </p>
     *
     * @param plateDetectContext 车牌识别上下文对象
     */
    @Override
    public void processOut(PlateDetectContext plateDetectContext) {
        //能走到这 一定录入系统了

        CommonVehicleEntity commonVehicleEntity = plateDetectContext.getCommonVehicleEntity();
        // 校验是否绑定运输车辆信息，未绑定则抛出异常
        if (commonVehicleEntity.getAssociationId() == null) {
            throw VehicleAccessException.SYSTEM_ERROR.newInstance("车辆未绑定运输车辆");
        }


        // 查询对应的运输车辆记录，若未找到则抛出异常
        TransportVehicleEntity transportVehicleEntity = transportVehicleService.getTransportVehicleById(commonVehicleEntity.getAssociationId());
        if (transportVehicleEntity == null) {
            throw VehicleAccessException.DATE_NOT_EXIST.newInstance("车辆不存在");
        }

        plateDetectContext.setTransportVehicleEntity(transportVehicleEntity);

    }

    /**
     * 记录运输车辆进场台账信息
     * <p>
     * 将普通车辆的进场信息同步到运输车辆台账中，并建立关联关系。
     * </p>
     *
     * @param plateDetectContext 车牌识别上下文对象
     */
    @Override
    public void recordIn(PlateDetectContext plateDetectContext) {
        super.recordIn(plateDetectContext);

        // 创建运输车辆台账记录实体对象
        VehicleTransportLedgerEntity vehicleTransportLedgerEntity = new VehicleTransportLedgerEntity();
        // 设置车辆编号
        vehicleTransportLedgerEntity.setVehicleNumber(plateDetectContext.getVehicleNumber());

        TransportVehicleEntity transportVehicleEntity = plateDetectContext.getTransportVehicleEntity();
        vehicleTransportLedgerEntity.setTransportVehicleType(transportVehicleEntity.getTransportVehicleType());

        VehicleCommonLedgerEntity vehicleCommonLedgerEntity = plateDetectContext.getVehicleCommonLedgerEntity();
        // 将普通车辆进场图片、相机信息、时间等拷贝到运输台账
        vehicleTransportLedgerEntity.setEntryPlateImgUrl(vehicleCommonLedgerEntity.getEntryPlateImgUrl());
        vehicleTransportLedgerEntity.setEntryVehicleImgUrl(vehicleCommonLedgerEntity.getEntryVehicleImgUrl());
        vehicleTransportLedgerEntity.setEntryCameraIp(vehicleCommonLedgerEntity.getEntryCameraIp());
        vehicleTransportLedgerEntity.setEntryTime(vehicleCommonLedgerEntity.getEntryTime());
        vehicleTransportLedgerEntity.setEntryUploadStatus(GovUploadStatus.INIT.name());

        // 插入新的运输车辆进场台账记录
        vehicleTransportLedgerService.insert(vehicleTransportLedgerEntity);

        // 更新普通车辆台账与运输车辆台账的关联关系
        vehicleCommonLedgerService.updateAssId(vehicleCommonLedgerEntity.getId(), vehicleTransportLedgerEntity.getId());

        plateDetectContext.setVehicleTransportLedgerEntity(vehicleTransportLedgerEntity);

    }

    /**
     * 记录运输车辆出场台账信息
     * <p>
     * 根据普通车辆台账信息创建或更新对应的运输车辆出场记录。
     * 若普通台账存在关联ID，则执行更新操作；否则新增新记录。
     * </p>
     *
     * @param plateDetectContext 车牌识别上下文对象
     */
    @Override
    public void recordOut(PlateDetectContext plateDetectContext) {
        super.recordOut(plateDetectContext);

        // 获取普通车辆台账信息
        VehicleCommonLedgerEntity vehicleCommonLedgerEntity = plateDetectContext.getVehicleCommonLedgerEntity();
        // 创建运输车辆台账记录对象并填充基础信息
        VehicleTransportLedgerEntity vehicleTransportLedgerEntity = new VehicleTransportLedgerEntity();
        vehicleTransportLedgerEntity.setVehicleNumber(plateDetectContext.getVehicleNumber());
        TransportVehicleEntity transportVehicleEntity = plateDetectContext.getTransportVehicleEntity();
        vehicleTransportLedgerEntity.setTransportVehicleType(transportVehicleEntity.getTransportVehicleType());

        vehicleTransportLedgerEntity.setExitPlateImgUrl(vehicleCommonLedgerEntity.getExitPlateImgUrl());
        vehicleTransportLedgerEntity.setExitVehicleImgUrl(vehicleCommonLedgerEntity.getExitVehicleImgUrl());
        vehicleTransportLedgerEntity.setExitCameraIp(vehicleCommonLedgerEntity.getExitCameraIp());
        vehicleTransportLedgerEntity.setExitTime(vehicleCommonLedgerEntity.getExitTime());
        vehicleTransportLedgerEntity.setExitUploadStatus(GovUploadStatus.INIT.name());

        // 若普通台账未绑定运输台账，说明是首次出场记录，执行插入操作
        if (vehicleCommonLedgerEntity.getAssociationId() == null) {
            //新增一条记录
            vehicleTransportLedgerService.insert(vehicleTransportLedgerEntity);
            vehicleCommonLedgerService.updateAssId(vehicleCommonLedgerEntity.getId(), vehicleTransportLedgerEntity.getId());

        } else {
            // 若已绑定，则更新现有运输车辆台账记录
            //更新记录 id = vehicleCommonLedgerEntity.assId这一条记录
            vehicleTransportLedgerEntity.setId(vehicleCommonLedgerEntity.getAssociationId());
            vehicleTransportLedgerService.updateTransportExitInfo(vehicleTransportLedgerEntity);
        }

        // 将更新后的运输台账实体放入上下文，供后续流程使用
        plateDetectContext.setVehicleTransportLedgerEntity(vehicleTransportLedgerEntity);




    }
}
